package org.fastsyncer.common.util;

import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.FileWriter;
import java.io.IOException;
import java.util.Map;
import java.util.Properties;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

public abstract class PropertiesUtil {

    private final static Logger logger = LoggerFactory.getLogger(PropertiesUtil.class);

    /**
     * 修改properties文件属性
     * @param proPath properties文件路径
     * @param key 要修改的key
     * @param value 要修改的值
     * @return true:成功,false:失败
     */
    public static boolean update(String proPath, String key, String value) {
        // 检查文件路径
        if (null == proPath || "".equals(proPath.trim())) {
            return false;
        }
        if (null == key || "".equals(key.trim()) || null == value) {
            return false;
        }

        // 读取配置文件
        StringBuffer str = null;
        boolean handle = false;
        FileReader reader = null;
        BufferedReader br = null;
        try {
            reader = new FileReader(proPath);
            br = new BufferedReader(reader);
            str = new StringBuffer();

            String line = "";
            while ((line = br.readLine()) != null) {
                // 处理空行
                if ("".equals(line)) {
                    str.append("\n");
                    continue;
                }

                // 处理注释
                if (line.startsWith("#")) {
                    str.append(line);
                    str.append("\n");
                    continue;
                }

                // 如果不是匹配得key范围,继续读取追加
                if (!line.trim().startsWith(key)) {
                    str.append(line);
                    str.append("\n");
                    continue;
                }

                // 如果不是相同key,继续读取追加
                String[] keyAndVal = line.split("=");
                if (!keyAndVal[0].trim().equals(key)) {
                    str.append(line);
                    str.append("\n");
                    continue;
                }

                // 如果是该key
                str.append(key + "=" + value);
                str.append("\n");
                handle = true;
            }
        } catch (IOException e) {
            logger.error(e.getClass() + ">>" + e.getMessage() + ">>" + e.getStackTrace().toString());
        } finally {
            if (null != br) {
                try {
                    br.close();
                } catch (IOException e) {
                    logger.error(e.getClass() + ">>" + e.getMessage() + ">>" + e.getStackTrace().toString());
                }
            }
            if (null != reader) {
                try {
                    reader.close();
                } catch (IOException e) {
                    logger.error(e.getClass() + ">>" + e.getMessage() + ">>" + e.getStackTrace().toString());
                }
            }
        }

        // 保存文件
        if (null == str) {
            return false;
        }

        FileWriter out = null;
        BufferedWriter bw = null;
        try {
            out = new FileWriter(proPath);
            bw = new BufferedWriter(out);
            bw.write(str.toString());
        } catch (IOException e) {
            logger.error(e.getClass() + ">>" + e.getMessage() + ">>" + e.getStackTrace().toString());
        } finally {
            if (null != bw) {
                try {
                    bw.close();
                } catch (IOException e) {
                    logger.error(e.getClass() + ">>" + e.getMessage() + ">>" + e.getStackTrace().toString());
                }
            }
            if (null != out) {
                try {
                    out.close();
                } catch (IOException e) {
                    logger.error(e.getClass() + ">>" + e.getMessage() + ">>" + e.getStackTrace().toString());
                }
            }
        }
        return handle;
    }

    /**
     * 修改properties文件属性
     * @param proPath properties文件路径
     * @param map 要修改的值
     */
    public static void update(String proPath, Map<String, String> map) {
        // 检查文件路径
        if (null == proPath || "".equals(proPath.trim())) {
            return;
        }
        if (null == map) {
            return;
        }

        // 读取配置文件
        StringBuffer str = null;
        FileReader reader = null;
        BufferedReader br = null;
        try {
            reader = new FileReader(proPath);
            br = new BufferedReader(reader);
            str = new StringBuffer();

            String line = "";
            while ((line = br.readLine()) != null) {
                // 处理空行
                if ("".equals(line)) {
                    str.append("\n");
                    continue;
                }

                // 处理注释
                if (line.startsWith("#")) {
                    str.append(line);
                    str.append("\n");
                    continue;
                }

                // 分割key=value
                String[] keyAndVal = line.split("=");
                // 取出key
                String keyStr = keyAndVal[0].trim();
                // 如果不是修改的key,继续追加
                if (null == map.get(keyStr)) {
                    str.append(line);
                    str.append("\n");
                    continue;
                }

                // 如果是要修改的key
                str.append(keyStr + "=" + map.get(keyStr));
                str.append("\n");
                // 清除该key
                map.remove(keyStr);
            }
        } catch (IOException e) {
            logger.error(e.getClass() + ">>" + e.getMessage() + ">>" + e.getStackTrace().toString());
        } finally {
            if (null != br) {
                try {
                    br.close();
                } catch (IOException e) {
                    logger.error(e.getClass() + ">>" + e.getMessage() + ">>" + e.getStackTrace().toString());
                }
            }
            if (null != reader) {
                try {
                    reader.close();
                } catch (IOException e) {
                    logger.error(e.getClass() + ">>" + e.getMessage() + ">>" + e.getStackTrace().toString());
                }
            }
        }

        // 保存文件
        if (null == str) {
            return;
        }

        FileWriter out = null;
        BufferedWriter bw = null;
        try {
            out = new FileWriter(proPath);
            bw = new BufferedWriter(out);
            bw.write(str.toString());
        } catch (IOException e) {
            logger.error(e.getClass() + ">>" + e.getMessage() + ">>" + e.getStackTrace().toString());
        } finally {
            if (null != bw) {
                try {
                    bw.close();
                } catch (IOException e) {
                    logger.error(e.getClass() + ">>" + e.getMessage() + ">>" + e.getStackTrace().toString());
                }
            }
            if (null != out) {
                try {
                    out.close();
                } catch (IOException e) {
                    logger.error(e.getClass() + ">>" + e.getMessage() + ">>" + e.getStackTrace().toString());
                }
            }
        }
    }

    public static Properties load(String proPath) {
        File f = new File(proPath);
        if (!f.exists()) {
            return null;
        }
        Properties pro = new Properties();
        FileReader fr = null;
        BufferedReader reader = null;
        try {
            fr = new FileReader(f);
            reader = new BufferedReader(fr);
            pro.load(reader);
        } catch (FileNotFoundException e) {
            logger.error(e.getClass().getName(), e.getLocalizedMessage());
        } catch (IOException e) {
            logger.error(e.getClass().getName(), e.getLocalizedMessage());
        } finally {
            if (null != reader) {
                try {
                    reader.close();
                } catch (IOException e) {
                }
            }
            if (null != fr) {
                try {
                    fr.close();
                } catch (IOException e) {
                }
            }
        }
        return pro;
    }

    //    public static void main(String[] args) {
    //        HashMap<String, String> map = new HashMap<>();
    //        map.put(CommonConstant.WORKER_TASK_MAX_NUMBER, "500");
    //        map.put(CommonConstant.WORKER_BATCH_NUMBER, "50");
    //        map.put(CommonConstant.WORKER_THREAD_NUMBER, "10");
    //        map.put(CommonConstant.CONFIG_ADMIN_PWD, "YWRtaW4=");
    //
    //        String proPath = "/D:/eclipse/workspace/fastsyncer/fastsyncer-common/target/classes/application.properties";
    //        PropertiesUtil.update(proPath, map);
    //        logger.info("ok");
    //    }

}
